package com.ldoublem.loadingviewlib.view;

import ohos.agp.animation.Animator;
import ohos.agp.animation.AnimatorValue;
import ohos.agp.components.AttrSet;
import ohos.agp.components.Component;
import ohos.agp.render.BlurDrawLooper;
import ohos.agp.render.Canvas;
import ohos.agp.render.LinearShader;
import ohos.agp.render.Paint;
import ohos.agp.render.Path;
import ohos.agp.render.PixelMapHolder;
import ohos.agp.render.Shader;
import ohos.agp.render.Texture;
import ohos.agp.utils.Color;
import ohos.agp.utils.Point;
import ohos.agp.utils.RectFloat;
import ohos.app.Context;
import ohos.media.image.PixelMap;
import ohos.media.image.common.Size;

import com.ldoublem.loadingviewlib.view.base.LVBase;

import static ohos.agp.render.Paint.Join.ROUND_JOIN;
import static ohos.agp.render.Paint.ShaderType.LINEAR_SHADER;
import static ohos.agp.render.Paint.StrokeCap.ROUND_CAP;
import static ohos.media.image.common.PixelFormat.ARGB_8888;



public class LVRingProgress extends LVBase implements Component.EstimateSizeListener, Component.DrawTask {

    private Paint mPaint;
    private PixelMap mBitmapBg ;
    private Paint mPaintText;
    private float MaxAngle = 359f;
    private int mPadding;
    private int mWidth;
    private int getMeasuredWidth;
    private int getMeasuredHeight;
    private RectFloat rectFBg = new RectFloat();
    private int Progress = 0;

    public LVRingProgress(Context context) {
        super(context);
    }

    public LVRingProgress(Context context, AttrSet attrs) {
        super(context, attrs);
    }

    public LVRingProgress(Context context, AttrSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
    }

    public int getProgress() {
        return Progress;
    }

    public void setProgress(int progress) {
        Progress = progress;
        invalidate();
    }


    private void initPaint() {
        addDrawTask(this);
        setEstimateSizeListener(this);
        mPaint = new Paint();
        mPaintText = new Paint();
        mPaintText.setAntiAlias(true);
        mPaintText.setStyle(Paint.Style.FILL_STYLE);
        mPaintText.setColor(Color.WHITE);

    }


    public void setViewColor(int color) {
        mPaint.setColor(new Color(color));
        invalidate();
    }

    public void setTextColor(int color) {
        mPaintText.setColor(new Color(color));
        invalidate();
    }


    public void setPorBarStartColor(int color) {
        ProStartColor = color;
    }

    public void setPorBarEndColor(int color) {
        ProEndColor = color;
    }

    private PixelMap getmBitmapBg(Paint paint) {
        Canvas canvas = null;

        if (mBitmapBg == null) {

            PixelMap.InitializationOptions initializationOptions = new PixelMap.InitializationOptions();
            initializationOptions.size = new Size(getMeasuredWidth, getMeasuredHeight);
            initializationOptions.pixelFormat = ARGB_8888;
            mBitmapBg = PixelMap.create(initializationOptions);
            canvas  = new Canvas(new Texture(mBitmapBg));

            paint.setAntiAlias(true);
            paint.setStrokeWidth(mPadding);
            paint.setStyle(Paint.Style.STROKE_STYLE);
            Path pathBg = new Path();
            pathBg.addArc(rectFBg, 0, 360);
            paint.setBlurDrawLooper(new BlurDrawLooper(mPadding / 3,
                    0,
                    mPadding / 4, new Color(Color.argb(100, 0, 0, 0))));
            canvas.drawPath(pathBg, paint);


        }

        return mBitmapBg;

    }


    private void drawBg(Canvas canvas, Paint paint) {
        canvas.drawPixelMapHolder(new PixelMapHolder(getmBitmapBg(paint)), 0
                , 0, paint);


    }


    int ProStartColor = Color.argb(100, 0, 242, 123);
    int ProEndColor = Color.argb(100, 86, 171, 228);

    private void drawProgress(Canvas canvas, Paint paint, int sweepAngle) {
        paint.reset();
        paint.setAntiAlias(true);
        paint.setStrokeWidth(mPadding);
        paint.setStyle(Paint.Style.STROKE_STYLE);

        Path pathProgress = new Path();
        pathProgress.addArc(rectFBg, -90, sweepAngle);

        Shader mShader = new LinearShader(
                new Point[]{new Point(rectFBg.left, rectFBg.top), new Point(rectFBg.left, rectFBg.bottom)},
                new float[]{0f, 1f},
                new Color[]{new Color(ProStartColor), new Color(ProEndColor)},
                Shader.TileMode.CLAMP_TILEMODE);

        paint.setShader(mShader,LINEAR_SHADER);
        paint.setStrokeCap(ROUND_CAP);
        paint.setStrokeJoin(ROUND_JOIN);
        canvas.drawPath(pathProgress, paint);

        mPaintText.setTextSize((int) (mPaint.getStrokeWidth() / 2));
        String text = (int) (sweepAngle / MaxAngle * 100) + "%";
        canvas.drawTextOnPath(mPaintText,text
                ,
                pathProgress,
                (float) (Math.PI * rectFBg.getWidth()
                                        * (sweepAngle / MaxAngle)
                                        - getFontlength(mPaintText, text) * 1.5f),
                getFontHeight(mPaintText) / 3
        );


    }






    private float mAnimatedValue = 0f;


    @Override
    protected void InitPaint() {
        initPaint();
    }

    @Override
    protected void OnAnimationUpdate(AnimatorValue valueAnimator, float v) {
        mAnimatedValue = v;
        setProgress((int) (mAnimatedValue * 100));
    }





    @Override
    protected void OnAnimationRepeat(Animator animation) {

    }

    @Override
    protected int OnStopAnim() {
        mAnimatedValue = 0f;
        invalidate();
        return 1;
    }

    @Override
    protected int SetAnimRepeatMode() {
        return RESTART;
    }

    @Override
    protected int SetAnimRepeatCount() {
        return 0;
    }


    @Override
    protected void AinmIsRunning() {

    }


    @Override
    public void onDraw(Component component, Canvas canvas) {
        canvas.save();
        mPadding = mWidth / 10;//dip2px(12);

        rectFBg = new RectFloat(getMeasuredWidth / 2 - mWidth / 2 + mPadding
                , getMeasuredHeight / 2 - mWidth / 2 + mPadding
                , getMeasuredWidth / 2 + mWidth / 2 - mPadding
                , getMeasuredHeight / 2 + mWidth / 2 - mPadding);

        drawBg(canvas, mPaint);
        drawProgress(canvas, mPaint, (int) (MaxAngle / 100f * getProgress()));
        canvas.restore();
    }

    @Override
    public boolean onEstimateSize(int i, int i1) {
        getMeasuredHeight = EstimateSpec.getSize(i1);
        getMeasuredWidth =EstimateSpec.getSize(i);
        if (getMeasuredWidth > getHeight())
            mWidth = getMeasuredHeight;
        else
            mWidth = getMeasuredWidth;
        return false;
    }
}
